package org.common.utils.rpc;
import org.common.utils.net.netty.NettyServer;
import org.common.utils.rpc.core.Const;
import org.common.utils.rpc.core.RpcImplementPool;
import org.common.utils.rpc.net.RpcNettyDeCode;
import org.common.utils.rpc.net.RpcNettyEnCode;
import org.common.utils.rpc.net.RpcNettyInitializer;
import org.common.utils.rpc.net.handler.RpcServerNettyHandler;
import org.common.utils.rpc.net.serialization.RpcFurySerialization;
import org.common.utils.rpc.net.serialization.RpcSerialization;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.concurrent.Executor;

/**
 * RPC服务端
 * @author zhouzhibing
 * @date 2025/11/14 23:11
 */
public class RpcServer {

    private static final Logger log = LoggerFactory.getLogger(RpcServer.class);

    /**
     * RPC接口实现对象池
     */
    private final RpcImplementPool implementPool;
    /**
     * netty网络服务
     */
    private final NettyServer nettyServer;
    /**
     * 端口
     */
    private final int port;


    public RpcServer(String packageName , int port) {
        this(packageName , new RpcFurySerialization() , port , null);
    }

    /**
     * 创建RPC服务端，会根据服务列表，和默认的Fury序列化方式进行序列化。
     * @param packageName 包名
     * @param port 端口
     */
    public RpcServer(String packageName , int port , Executor executor) {
        this(packageName , new RpcFurySerialization() , port , executor);
    }

    /**
     * 创建RPC服务端，会根据服务列表，和指定序列化方式进行序列化。
     * @param packageName 包名
     * @param serializable 序列化方式
     * @param port 端口
     */
    public RpcServer(String packageName , RpcSerialization serializable , int port , Executor executor) {
        this.implementPool = new RpcImplementPool(packageName);
        this.nettyServer = newNettyServer(serializable , executor);
        this.port = port;
    }

    /**
     * 初始化网络
     */
    private NettyServer newNettyServer(RpcSerialization serializable, Executor executor) {
        RpcNettyEnCode enCode = new RpcNettyEnCode(serializable);
        RpcNettyDeCode deCode = new RpcNettyDeCode(serializable);
        RpcServerNettyHandler handler = new RpcServerNettyHandler(this.implementPool , executor);
        RpcNettyInitializer initializer = new RpcNettyInitializer(Const.SERVER_NAME, enCode, deCode, handler);
        log.info("RpcServer init success");
        return new NettyServer(initializer);
    }

    /**
     * 启动服务
     */
    public void start() {
        nettyServer.start(port);
        log.info("RpcServer start success , port : [{}]" , port);
    }
}
